<?php

namespace App\Http\Controllers;

use App\Datas\AfLog;
use App\Datas\ModelList;
use App\Datas\ModelStyle;
use App\Datas\System;
use App\Datas\User;
use App\Datas\Pay;
use App\Datas\UserDrawing;
use App\Datas\Opus;
use App\Datas\UserOntrial;
use App\Datas\UserStyle;
use App\Tools\FunTool;
use App\Tools\IPFactory;
use App\Tools\JSWechat;
use App\Tools\Oppo;
use App\Tools\Qq;
use App\Tools\Shumei;
use App\Tools\Wechat;
use AppleSignIn\ASDecoder;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\DB;
use Ixudra\Curl\Facades\Curl;
use Illuminate\Support\Facades\Log;
use Illuminate\Support\Facades\Redis;


class UserController extends Controller {

	protected $dataUser;
	protected $dataUserOntrial;
	protected $dataOpus;
	protected $dataPay;

	/**
	 * Create a new controller instance.
	 *
	 * @return void
	 */
	public function __construct() {
		$this->dataUser = new User();
		$this->dataOpus = new Opus();
		$this->dataPay = new Pay();
		$this->dataUserOntrial = new UserOntrial();
		$this->repeatKeyTime = 10;
	}


	/**
	 * 苹果登录
	 * @param Request $request
	 */
	public function loginApple(Request $request) {
		$this->validate($request, [
			'identity_token' => ['required'], 'user' => ['required'],
		]);

		$identityToken = $request->post('identity_token');
		$clientUser = $request->post('user');
		$af_id = $request->post("appsflyer_id");
		$email = $request->post("email",'');

		$deviceId = $this->getDeviceId();

		$res = $this->checkRepeatLogin($deviceId.'-'.$clientUser);

		if (!$res) {
			return $this->buildReturn(Code::PARAM_ERROR);
		}

		$appleSignInPayload = ASDecoder::getAppleSignInPayload($identityToken);
		$isValid = $appleSignInPayload->verifyUser($clientUser);
		if(!$isValid) {
			return $this->buildReturn(Code::PARAM_ERROR);
		}

		// 查看用户是否存在
		$userInfo = $this->dataUser->getUserApple($clientUser);

		//AF归因渠道
		$af_media_source = "organic";
		if(!empty($af_id)) {
			$afInfo = AfLog::getInstance()->getInfo([
				"appsflyer_id" => $af_id, "platform" => 1
			]);
			$af_media_source = !empty($afInfo) ? $afInfo["media_source"] : $af_media_source;
		}

		// 用户不存在 创建用户
		if(!$userInfo) {
			$userId = $this->dataUser->addUser('', '', '', $clientUser, '', '', '', $deviceId, "", 1, $af_media_source, $email);
			$userInfo = [
				'id' => $userId, 'nickname' => '', 'phone' => '', 'google' => '', 'apple' => $clientUser,
				'weixin' => '', 'qq' => '',
			];
			$this->pushReg();
		} else {
			if(empty($userInfo["channel"])) {
				$this->dataUser->updateChannel($userInfo['id'], $af_media_source);
			}
		}

		// 设置用户session
		$token = $this->setTokenUser($userInfo['id']);
		$userInfo['token'] = $token;

		//检查下需要更新的订单
		if($this->checkNoLoginPay()) {
			$this->dataPay->updateUserIdByDeviceId($deviceId, $userInfo["id"], 1);
		}

		$this->dataUser->updateNoLoginData($deviceId, $userInfo['id'], 1);

		// 返回用户
		return $this->buildReturn(Code::SUCCESS, $userInfo);
	}

	/**
	 * google登录
	 * @param Request $request
	 */
	public function loginGoogle(Request $request) {
		$this->validate($request, [
			'key' => ['required'],
		]);

		$key = $request->post('key');

		$deviceId = $this->getDeviceId();

		$res = $this->checkRepeatLogin($deviceId.'-'.$key);
		if (!$res) {
			return $this->buildReturn(Code::PARAM_ERROR);
		}
		// 查看用户是否存在
		$userInfo = $this->dataUser->getUserGoogle($key);
        $af_id = $request->post("appsflyer_id");
        $email = $request->post("email",'');

		$version = $this->getVersion();
		
		//新版本这里判断这个设备是否有交易产生
		$isPay = false;
		if(version_compare($version, "1.6.0") >= 0) {
			$userByDevice = $this->dataUser->getUserByDevice($deviceId);
			if ($userByDevice) {
				$payFirst = $this->dataPay->getFirst($userByDevice['id']);
				$isPay = $payFirst ? true : false;
			}
		} else {
			$userByDevice['google'] = "";
		}

		//AF归因渠道
		$af_media_source = "organic";
		if(!empty($af_id)) {
			$afInfo = AfLog::getInstance()->getInfo([
				"appsflyer_id" => $af_id, "platform" => 2
			]);
			$af_media_source = !empty($afInfo) ? $afInfo["media_source"] : $af_media_source;
		}

		// 用户不存在 创建用户
		if(!$userInfo) {
			$userId = $this->dataUser->addUser('', '', $key, '', '', '', '', $deviceId, "", 1, $af_media_source, $email);
			$userInfo = [
				'id' => $userId, 'nickname' => '', 'phone' => '', 'google' => $key, 'apple' => '', 'weixin' => '',
				'qq' => '',
			];
			$this->pushReg();
		} else {
			if(empty($userInfo["channel"])) {
				$this->dataUser->updateChannel($userInfo['id'], $af_media_source);
			}
		}

		// 设置用户session
		$token = $this->setTokenUser($userInfo['id']);
		$userInfo['token'] = $token;

		if($isPay && $userByDevice['google'] == "") {
			//迁移会员剩余时长以及点数(用户表，订单表，点数记录表)
			$oldUserId = $userByDevice['id'];
			$newUserId = $userInfo['id'];
			$this->dataPay->updatePayData($oldUserId, $newUserId);
			$this->dataUser->updateDotData($oldUserId, $newUserId);
			$this->dataUser->updateDotNew($newUserId, $userByDevice['dot']);
			$cha = $userByDevice['vip_exp'] - time();
			if($cha > 0) {
				$this->dataUser->updateVipExp($newUserId, $cha, 'vip_exp');
			}

			$this->dataUser->delete($oldUserId);
		}

		$this->dataOpus->freePut($userInfo['id'], $deviceId);

		//检查下需要更新的订单
		if($this->checkNoLoginPay()) {
			$this->dataPay->updateUserIdByDeviceId($deviceId, $userInfo["id"], 2);
		}

		// 返回用户
		return $this->buildReturn(Code::SUCCESS, $userInfo);
	}


	/**
	 * 微信登录
	 * @param Request $request
	 */
	public function loginJSWeixin(Request $request) {
		$this->validate($request, [
			'jscode' => ['required'],
		]);

		$jscode = $request->post('jscode');
		$channelId = $request->post('channel') ?? '100';
		$source = $request->post('source') ?? '';
		$cburl = $request->post('cburl') ?? '';

		$weixin = new JSWechat();
		$openId = $weixin->getJsOpenId($jscode);
		if(!$openId) {
			return $this->buildReturn(Code::PARAM_ERROR);
		}

		$res = $this->checkRepeatLogin($openId.'-'.$openId);
		if (!$res) {
			return $this->buildReturn(Code::PARAM_ERROR);
		}
		// 查看用户是否存在
		$userInfo = $this->dataUser->getUserJSWeixin($openId);
		$deviceId = $openId;//$this->getDeviceId();
		$version = $this->getVersion();

		// 用户不存在 创建用户
		if(!$userInfo) {
			$sIP = IPFactory::Instance()->getClientIP();
			$sIPCountryCo = IPFactory::Instance()->getCountryCoByIP($sIP);

			$systemData = new System();
			$systemData->setDevice($deviceId, $channelId, '', '', '', '', '', '', '', '', '', '', '', '', $cburl, $source, $version,'', $sIP, $sIPCountryCo);
			$userId = $this->dataUser->addUser('', '', '', '', '', $openId, '', $deviceId);
			$userInfo = [
				'id' => $userId, 'nickname' => '', 'phone' => '', 'google' => '', 'apple' => '', 'weixin' => '',
				'jsweixin' => $openId, 'qq' => ''
			];

			$this->pushReg($openId);
		}

		// 设置用户session
		$token = $this->setTokenUser($userInfo['id']);
		$userInfo['token'] = $token;

		// 返回用户
		return $this->buildReturn(Code::SUCCESS, $userInfo);
	}

	/**
	 * 微信登录
	 * @param Request $request
	 */
	public function loginWeixin(Request $request) {
		$this->validate($request, [
			'token' => ['required'], 'refresh_token' => ['required'],
		]);

		$token = $request->post('token');
		$refreshToken = $request->post('refresh_token');
		$pkg = $this->getPkg();
		$weixin = new Wechat($pkg);
		$openId = '';
		$wxUserInfo = $weixin->run($token, $refreshToken, $openId);
		if(!$wxUserInfo) {
			return $this->buildReturn(Code::PARAM_ERROR);
		}
		$openId = $wxUserInfo['openid'];

		$deviceId = $this->getDeviceId();

		$res = $this->checkRepeatLogin($deviceId.'-'.$openId);
		if (!$res) {
			return $this->buildReturn(Code::PARAM_ERROR);
		}
		// 查看用户是否存在
		$userInfo = $this->dataUser->getUserWeixin($openId);

		// 用户不存在 创建用户
		if(!$userInfo) {
			$userId = $this->dataUser->addUser($wxUserInfo['nickname'], '', '', '', $openId, '', '', $deviceId, $wxUserInfo['portrait'], 0);
			$userInfo = [
				'id' => $userId, 'nickname' => $wxUserInfo['nickname'], 'phone' => '', 'google' => '', 'apple' => '',
				'weixin' => $openId, 'qq' => '', 'image' => $wxUserInfo['portrait']
			];
			$this->pushReg();
		}

		// 设置用户session
		$token = $this->setTokenUser($userInfo['id']);
		$userInfo['token'] = $token;

		// 返回用户
		return $this->buildReturn(Code::SUCCESS, $userInfo);
	}


	/**
	 * QQ登录
	 * @param Request $request
	 */
	public function loginQq(Request $request) {
		$this->validate($request, [
			'token' => ['required'],
		]);

		$token = $request->post('token');
		$pkg = $this->getPkg();
		$qq = new Qq($pkg);
		$qqUserInfo = $qq->run($token);

		if(!$qqUserInfo) {
			return $this->buildReturn(Code::PARAM_ERROR, null);
		}

		$openId = $qqUserInfo['openid'];

		$deviceId = $this->getDeviceId();

        $res = $this->checkRepeatLogin($deviceId.'-'.$openId);
        if (!$res) {
			return $this->buildReturn(Code::PARAM_ERROR);
		}
		// 查看用户是否存在
		$userInfo = $this->dataUser->getUserQq($openId);

		// 用户不存在 创建用户
		if(!$userInfo) {
			$userId = $this->dataUser->addUser($qqUserInfo['nickname'], '', '', '', '', '', $openId, $deviceId, $qqUserInfo['portrait'], 0);
			$userInfo = [
				'id' => $userId, 'nickname' => $qqUserInfo['nickname'], 'phone' => '', 'google' => '', 'apple' => '',
				'weixin' => '', 'qq' => $openId, 'image' => $qqUserInfo['portrait']
			];
			$this->pushReg();
		}

		// 设置用户session
		$token = $this->setTokenUser($userInfo['id']);
		$userInfo['token'] = $token;

		// 返回用户
		return $this->buildReturn(Code::SUCCESS, $userInfo);
	}

	public function loginFacebook(Request $request) {
		$this->validate($request, [
			'token' => ['required'], 'id' => ['required']
		]);

		$token = $request->post('token');
		$id = $request->post('id');

		$this->dataUser->getFaceBookUser();
	}

	public function pushReg($openId = null) {
		$guid = $_SERVER['HTTP_GUID'] ?? null;
		if($openId) {
			$guid = $openId;
		}
		if(!$guid) {
			return false;
		}
		$systemData = new System();
		$deviceInfo = $systemData->getDevice($guid);
		$adSource = $deviceInfo['ad_source'] ?? '';
		$adCburl = $deviceInfo['ad_cburl'] ?? '';
		$platform = $deviceInfo['platform'] ?? '';
		$channelId = $deviceInfo['channel_id'] ?? '';
		if(!empty($adCburl) && $adSource == 'toutiao') {
			Curl::to($adCburl.'&event_type=1')->get();
		}
		if(!empty($adCburl) && $adSource == 'kuaishou') {
			Curl::to($adCburl.'&event_type=2&event_time='.time().'000')->get();
		}
		if(!empty($adCburl) && $adSource == 'wangyi') {
			$convAction = $platform == 'ios' ? 'ios_register' : 'android_register';
			$res = Curl::to('http://conv.youdao.com/api/track?conv_ext='.$adCburl.'&conv_action='.$convAction)->get();
			//writeLog('ad', "广告|网易|注册|结果", [$deviceInfo, $res]);
		}
		if(!empty($adCburl) && $adSource == 'bilibili') {
			$res = Curl::to($adCburl.'&conv_type=USER_REGISTER&conv_time='.time().'000')->get();
			//writeLog('ad', "广告|B站|注册|结果", [$deviceInfo, $res]);
		}
		// if ($channelId == '60003') {
		//     $oppoTools = new Oppo();
		//     $oppoTools->sendData($deviceInfo['imei'], $deviceInfo['oaid'],'','',2,'', 0, $adCburl);
		// }
		if($channelId == 'oppo-01') {
			$oppoTools = new Oppo();
			$oppoTools->sendData($deviceInfo['imei'], $deviceInfo['oaid'], '', '', 2, '', 1, $adCburl);
		}
		if(!empty($adCburl) && $adSource == 'jsbilibili') {
			$url = 'https://cm.bilibili.com/conv/api/conversion/ad/cb/v1?conv_type=FORM_SUBMIT&conv_time='.time().'000'.'&track_id='.$adCburl;
			$res = Curl::to($url)->get();
			//Log::info('jsbilibili-reg', [ 'ret' => $res ]);
		}
		if(!empty($adCburl) && $adSource == 'jstoutiao') {
			$url = 'https://analytics.oceanengine.com/api/v2/conversion';
			$data = [
				'event_type' => 'active_register', 'context' => [
					'ad' => [
						'callback' => $adCburl,
					]
				], 'timestamp' => time() * 1000
			];
			$retData = Curl::to($url)->withData($data)->asJsonRequest()->asJsonResponse()->post();
			Log::info('jstoutiao-reg', ['ret' => $retData, 'req' => $data]);
		}
	}

	/**
	 * 手机号注册登录
	 * @param Request $request
	 */
	public function loginPhone(Request $request) {

	}

	/**
	 * 获取手机验证码
	 * @param Request $request
	 */
	public function getSmsCode(Request $request) {

	}


	/**
	 * 删除用户
	 * @param Request $request
	 * @return array
	 */
	public function delete(Request $request) {
		$userId = $this->getTokenUser();

		if(!$userId) {
			return $this->buildReturn(Code::NOT_LOGIN);
		}

		$this->dataUser->delete($userId);

		$this->delTokenUser();
		return $this->buildReturn(Code::SUCCESS);
	}


	/**
	 * 设置昵称
	 * @param Request $request
	 */
	public function editNickname(Request $request) {
		$this->validate($request, [
			'nickname' => ['required'],
		]);

		$nickname = $request->post('nickname');
		$userId = $this->getTokenUser();

		if(!$userId) {
			return $this->buildReturn(Code::NOT_LOGIN);
		}

		$shumei = new Shumei();
		$nickname = $shumei->check($nickname);

		if($this->dataUser->findNickName($nickname)) {
			return $this->buildReturn(Code::RE_NICKNAME);
		}

		$this->dataUser->setNickname($userId, $nickname);

		return $this->buildReturn(Code::SUCCESS);
	}

	/**
	 * 设置图片
	 * @param Request $request
	 * @return array
	 * @throws \Illuminate\Validation\ValidationException
	 */
	public function editImage(Request $request) {
		$this->validate($request, [
			'image' => ['required'],
		]);

		$image = $request->post('image');
		$userId = $this->getTokenUser();

		if(!$userId) {
			return $this->buildReturn(Code::NOT_LOGIN);
		}

		$this->dataUser->setImage($userId, $image);

		return $this->buildReturn(Code::SUCCESS);
	}


	/**
	 * 获取当前登录用户信息
	 * @param Request $request
	 * @return array
	 */
	public function getCurUser(Request $request) {
		$userId = $this->getTokenUser();

		if(!$userId) {
			return $this->buildReturn(Code::NOT_LOGIN);
		}

		$data = $this->dataUser->getUser($userId);
		/*$dataPay = new Pay();
		$payData = $dataPay->getFirst($userId);
		if($payData) {
			$data['first_pay_date'] = strtotime($payData['pay_at']);
		}*/

		$data['dh_dot'] = 0;

		$isCheck = $request->get('is_check');
		if(isset($isCheck) && $isCheck == 1) {
			$dot = $this->dataUser->getDhNum($userId);
			$data['dh_dot'] = $dot;
		}

		if($userId) {
			$this->dataUser->setActive($userId);
		}

		$experInfo = $this->dataUserOntrial->getStatus($userId);
        Log::info("getCurUser",["user_id" => $userId,"data" => $data,"experInfo" => $experInfo]);
		if ($experInfo) {
			//说明还在试用期
			if ($experInfo['exper_time'] - time() > 0) {
				if ($experInfo['exper_product'] == "golden-vip") {
					$day = 365;
				}
				if ($experInfo['exper_product'] == "weekly-pro") {
					$day = 7;
				}

				$cha = $day * 24 * 3600 -  (time() - $experInfo['created_at']);
				$data['vip_surplus'] = $cha;
				if ($data['vip_surplus'] < 0) {
					$data['vip_surplus'] = 0;
				}
				if ($data['vip_surplus']/(3600*24*365) > 50) {
					$data['vip_surplus'] = -1;
				}
			}
		}

		//获取用户画板解锁状态
		$userDrawing = new UserDrawing();
		$userDrawData = $userDrawing->getUserDraw($userId);
		$data['drawing_data'] = array_column($userDrawData, 'drawing_id');

		return $this->buildReturn(Code::SUCCESS, $data);
	}

	/**
	 * 获取用户作品生成信息
	 */
	public function getOpusInfo(Request $request) {
		$userId = $this->getTokenUser();
		if(!$userId) {
			return $this->buildReturn(Code::NOT_LOGIN);
		}

		$data['point'] = config("app.opus_dot");

		return $this->buildReturn(Code::SUCCESS, $data);
	}

	public function loginNew(Request $request) {
		$deviceId = $this->getDeviceId();
		if(!$deviceId) {
			return $this->buildReturn(Code::ERROR);
		}

		$userInfo = $this->dataUser->getUserByDevice($deviceId);
		$isPay = $this->dataPay->getFirst($userInfo['id']);

		$token = $this->setTokenUser($userInfo['id']);
		$userInfo['token'] = $token;

		$userInfo['is_pay'] = $isPay ? true : false;

		// 返回用户
		return $this->buildReturn(Code::SUCCESS, $userInfo);
	}

	/**
	 * 恢复购买
	 */
	public function restoreApple(Request $request) {
		$this->validate($request, [
			'identity_token' => ['required'], 'user' => ['required'],
		]);

		$identityToken = $request->post('identity_token');
		$clientUser = $request->post('user');
		$af_id = $request->post("appsflyer_id");

		$appleSignInPayload = ASDecoder::getAppleSignInPayload($identityToken);
		$isValid = $appleSignInPayload->verifyUser($clientUser);
		if(!$isValid) {
			return $this->buildReturn(Code::PARAM_ERROR);
		}

		// 查看用户是否存在
		$userInfo = $this->dataUser->getUserApple($clientUser);

		//$deviceId = $this->getDeviceId();

		//AF归因渠道
		$af_media_source = "organic";
		if(!empty($af_id)) {
			$afInfo = AfLog::getInstance()->getInfo([
				"appsflyer_id" => $af_id, "platform" => 1
			]);
			$af_media_source = !empty($afInfo) ? $afInfo["media_source"] : $af_media_source;
		}


		// 用户不存在 创建用户
		if(!$userInfo) {
			//$userId = $this->dataUser->addUser('', '', '', $clientUser, '', '', '', $deviceId, "", 1, $af_media_source);
			//$userInfo = [
			//	'id' => $userId, 'nickname' => '', 'phone' => '', 'google' => '', 'apple' => $clientUser,
			//	'weixin' => '', 'qq' => '',
			//];
			//$this->pushReg();
			return $this->buildReturn(Code::NOT_ECY_VIP);// 不是会员
		} else {
			if(empty($userInfo["channel"])) {
				$this->dataUser->updateChannel($userInfo['id'], $af_media_source);
			}
		}

		// 设置用户session
		$token = $this->setTokenUser($userInfo['id']);
		$userInfo['token'] = $token;

		//检查下需要更新的订单
		//if($this->checkNoLoginPay()) {
		//	$this->dataPay->updateUserIdByDeviceId($deviceId, $userInfo["id"], 1);
		//}

		// 返回用户
		return $this->buildReturn(Code::SUCCESS, $userInfo);
	}

	/**
	 * 我解锁的
	 */
    public function getMyStyleList(Request $request) {
        $page = intval($request->get('page',1));

        $return = [
            "page" => 0,
            "list" => new \stdClass(),
        ];
        $userId = $this->getTokenUser() ?? 0;
        //$userId = 1;
        if ($userId > 0) {

            $page = ($page < 1) ? 1 : $page;
            $limit = ($page - 1) * parent::PAGE_SIZE;

            $count = UserStyle::getInstance()->getCountByUserId($userId);

            $sql = "SELECT b.id,b.img,b.name,c.vip FROM " . FunTool::formateTable(UserStyle::getInstance()->tableName) . " AS a";
            $sql .= " LEFT JOIN " . FunTool::formateTable(ModelStyle::getInstance()->tableName ) . " AS b ON a.style_id = b.id";
            $sql .= " LEFT JOIN " . FunTool::formateTable(ModelList::getInstance()->tableName) . " AS c on b.model_id = c.id";
            $sql .= " WHERE a.user_id = {$userId} ORDER BY a.id DESC";
            $sql .= " LIMIT {$limit},".parent::PAGE_SIZE;
            $list = DB::select($sql);
            foreach ($list as &$item) {
                $item = (array)$item;
                ModelStyle::getInstance()->formatItem($item);
                $item["vip"] = $item["vip"] == ModelList::IS_VIP ? FunTool::getVipImg() : "";
            }

            $return["list"] = $list;
            if ($count > $limit + parent::PAGE_SIZE) {
                $return["page"] = $page + 1;
            } else {
                $return["page"] = 0;
            }
        }

        return $this->buildReturn(Code::SUCCESS,$return);
    }

    /**
     * 校验登录时重复请求，接口幂等性
     */
    public function checkRepeatLogin($uniqid){
    	$repeatKey = 'USER:REPEAT-'.$uniqid;
        $repeat = Redis::SETNX($repeatKey, 1);
        if ($repeat) {
        	Redis::EXPIRE($repeatKey, $this->repeatKeyTime);
        	return true;
        }else{
        	return false;
        }
    }

    public function getUserIsPay(Request $request){

    	$isPay = (new Pay())->getIsPay($this->getTokenUser(), $this->getDeviceId());

    	return $this->buildReturn(Code::SUCCESS,['is_pay'=>$isPay]);

    }
    /**
     * 获取是不是非会员老用户
     */
    public function getUserIsOldVip(Request $request){

    	$isOld = (new User())->getIsOldVip($this->getTokenUser(), $this->getDeviceId());

    	return $this->buildReturn(Code::SUCCESS,['is_old_vip'=>$isOld]);

    }




}
